// 封装一个函数 将 对象 转化为 键值对字符串
function getValStr( obj ){
    // 定义变量储存字符串
    let str = '' ;

    // 循环遍历对象 拼接成 字符串
    for( let key in obj ){
        str += `${key}=${obj[key]}&` ;
    }

    // 返回值结果 不要最后一个&符号
    return str.slice( 0 , -1 ); 

}

// 封装 ajax 函数
// 形参 valObj 存储 执行时 输入的实参数据
function myAjax( valObj ){
    // 定义一个对象 存储 ajax请求的默认值
    const defaultObj = {
        // 地址默认值是 空字符串
        url:'',
        // 请求方式默认值是 get
        type:'get',
        // 携带参数默认值是 ''
        data: '' ,
        // 请求成功回调函数 默认值是 空函数
        success:function(){},

        // 请求失败回调函数 默认值是 空函数
        error:function(){},
    }

    // 将实参对象中的数据 赋值给 默认值对象
    for( let key in defaultObj ){
        // 使用 默认值对象键名 从 实参对象中调用数据
        if( valObj[key] !== undefined ){
            // 如果调用结果不是 undefined 证明 实参数据中 存储了这个键名的数据
            // 给默认值对象这个键名 赋值 实参数据对象中这个键名存储的键值
            defaultObj[key] = valObj[key];
        }
    }

    // 如果 携带参数是对象类型 转化为 字符串类型
    if( typeof( defaultObj.data ) === 'object' ) defaultObj.data = getValStr( defaultObj.data );

    // 请求地址 不能是 空字符串 必须设定
    if( defaultObj.url === '' ) throw( 'url地址必须设定' );

    // 请求方式 必须是 get / post
    if( !( defaultObj.type.toLowerCase() === 'get' || defaultObj.type.toLowerCase() === 'post' ) ) throw( '请求方式必须是get/post' );

    // 创建 ajax 实例化对象
    const xhr = new XMLHttpRequest() ;

    // 判断请求方式 设定 不同的ajax配置
    if( defaultObj.type.toLowerCase() === 'get' ){
        // get请求方式设定

        // 在请求地址后携带参数
        xhr.open( 'get' , defaultObj.data === '' ? defaultObj.url : defaultObj.url + '?' + defaultObj.data  );
    
        // 发送请求
        xhr.send();
    
    }else if( defaultObj.type.toLowerCase() === 'post' ){
        // post请求方式设定

        // 设定 open()
        xhr.open( 'post' , defaultObj.url );

        // 设定请求头
        xhr.setRequestHeader( 'Content-Type' , 'application/x-www-form-urlencoded' );

        // 设定 send() 携带参数
        xhr.send( defaultObj.data );

    }

    // 获取 响应体结果 执行回调函数
    xhr.onload = function(){
        // ajax状态码是 4 并且 http状态码是 200 - 299 执行 请求成功的程序
        if( xhr.readyState === 4 && /^2\d{2}$/.test( xhr.status ) ) {
            // 执行回调函数时 输入的实参是 xhr.response 中 存储的 响应体结果
            defaultObj.success( xhr.response );

        }else{
            // 如果 ajax状态码不是 4 或者 http状态码不是 200 - 299 是 请求失败
            defaultObj.error();
        }
    }
}

// 封装 promise 函数 
// 创建 promise实例化对象对象 返回promise实例化对象
// 设定 promise要执行的异步程序
// 封装函数的参数 是 异步程序执行需要的参数数据
function myPromise( object ){
    // 创建promise实例化对象
    const p = new Promise(function( fulfilled , rejected ){
        // 设定要一直的异步程序
        myAjax( {
            // 数据参数等 是 调用函数时 输入的数据参数
            url: object.url ,
            type: object.type ,
            data: object.data,

            // 请求成功 请求失败 触发的函数程序 
            // 是 promise中 匿名函数 参数1 参数2 对应的 回调函数程序
            success: fulfilled ,
            error: rejected ,
        } );

    });

    // 返回promise实例化对象
    return p ;
}